package com.base.essearch.handler;

import com.alibaba.fastjson.JSONObject;
import com.base.essearch.utils.ServletUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.HashMap;
import java.util.Map;

/**
 * 统一异常处理
 *
 * @author lr
 * @date 2020/4/20
 */
@ControllerAdvice
public class GlobalExceptionHandler {

    private static final Logger logger = LoggerFactory.getLogger(GlobalExceptionHandler.class);
    public static final String CUSTOM_ERROR_MAP_NAME = "customErrorMap";


    /**
     * 自定义异常数据
     * 适配页面和Ajax请求
     * 注解ExceptionHandler(Exception.class)的Exception.class可以替换成自己定义的错误异常类
     *
     * @param request
     * @return
     */
    @ExceptionHandler(Exception.class)
    public String exceptionHandler(HttpServletRequest request, HttpServletResponse response, Exception ex) {
        logger.error("ExceptionHandler  exception: ", ex);
        //   request.setAttribute(CUSTOM_ERROR_MAP_NAME, map);
        //传入自己的错误代码，必须的，否则不会进入自定义错误页面，见：org.springframework.boot.autoconfigure.web.AbstractErrorController
        request.setAttribute("javax.servlet.error.status_code", 500);
        // 如果是Ajax请求，返回Json字符串。
        if (ServletUtils.isAjaxRequest(request)) {
            Map<String, Object> map = new HashMap<>(4);
            map.put("errorCode", 500);
            map.put("errorMsg", "错误信息" + ex.getMessage());
            map.put("errorSystem", "errorSystem");
            return ServletUtils.renderString(response, JSONObject.toJSONString(map));
        }
        //转发到springBoot错误处理请求，能适配网页和Ajax的错误处理
        //请求/error后，会进入BasicErrorController(@RequestMapping("${server.error.path:${error.path:/error}}"))
        //页面的数据显示处理是使用：errorAttributes.getErrorAttributes获取显示的，是AbstractErrorController的方法
        //可以编写一个自定义错误属性类处理：CustomErrorAttribute，继承DefaultErrorAttributes，重写getErrorAttributes(RequestAttributes requestAttributes, boolean includeStackTrace)方法
        return "forward:/error";
    }

}
